home *** CD-ROM | disk | FTP | other *** search
- /*
- * WinLIB
- * Window routines
- */
-
- #include <stdlib.h>
- #include "winlib.h"
- #include "internal.h"
- #include "config.h"
-
- WIN *_wintree;
- int _moving_win, _has_win, _moving_idx;
-
- int _winstruct_length(void)
- {
- return(sizeof(struct _winstruct));
- }
-
- void _top_window_link(void)
- {
- while(_wintree->prev)
- _wintree = _wintree->prev;
- }
-
- void _bottom_window_link(void)
- {
- while(_wintree->next)
- _wintree = _wintree->next;
- }
-
- void _create_window(int x, int y, int w, int h, char *title, int mode)
- {
- int i;
-
- /* Create our window and work window structures */
- _wintree->win = newwin(h, w, y, x);
- _wintree->workwin = newwin(h - 2, w - 2, y + 1, x + 1);
- _wintree->pan = new_panel(_wintree->win);
- _wintree->workpan = new_panel(_wintree->workwin);
-
- /* Save window coordinate information */
- _wintree->cur.x = x; _wintree->orig.x = x;
- _wintree->cur.y = y; _wintree->orig.y = y;
- _wintree->cur.w = w; _wintree->orig.w = w;
- _wintree->cur.h = h; _wintree->orig.h = h;
-
- /* And let the work window become scrollable */
- scrollok(_wintree->workwin, TRUE);
-
- /* Draw the borders */
- for(i = 0; i < _wintree->win->_maxx; i++) {
- mvwaddch(_wintree->win, 0, i, ACS_DHLINE);
- mvwaddch(_wintree->win, _wintree->win->_maxy, i, ACS_DHLINE);
- }
-
- for(i = 0; i < _wintree->win->_maxy; i++) {
- mvwaddch(_wintree->win, i, 0, ACS_DVLINE);
- mvwaddch(_wintree->win, i, _wintree->win->_maxx, ACS_DVLINE);
- }
-
- /* Add the corners */
- mvwaddch(_wintree->win, 0, 0, ACS_DULCORNER);
- mvwaddch(_wintree->win, 0, _wintree->win->_maxx, ACS_DURCORNER);
- mvwaddch(_wintree->win, _wintree->win->_maxy, 0, ACS_DLLCORNER);
- mvwaddch(_wintree->win, _wintree->win->_maxy, _wintree->win->_maxx, ACS_DLRCORNER);
-
- /* And the title */
- i = (_wintree->win->_maxx - strlen(title)) / 2;
- mvwaddstr(_wintree->win, 0, i, title);
-
- /* Add a closer button if there is one */
- if (mode & CLOSER) {
- mvwaddch(_wintree->win, 0, 1, '[');
- mvwaddch(_wintree->win, 0, 2, ACS_BULLET);
- mvwaddch(_wintree->win, 0, 3, ']');
- }
-
- /* Add a mover indicator around the title bar if you can move the window */
- if (mode & MOVER) {
- mvwaddch(_wintree->win, 0, i - 1, ' ');
- mvwaddch(_wintree->win, 0, i - 2, '[');
- mvwaddch(_wintree->win, 0, i + strlen(title), ' ');
- mvwaddch(_wintree->win, 0, i + strlen(title) + 1, ']');
- }
-
- i = 0;
-
- /* Put a minimizer button in */
- if (mode & MINIMIZER) {
- mvwaddch(_wintree->win, 0, _wintree->win->_maxx - 1, ']');
- mvwaddch(_wintree->win, 0, _wintree->win->_maxx - 2, ACS_DARROW);
- mvwaddch(_wintree->win, 0, _wintree->win->_maxx - 3, '[');
- i = 3;
- }
-
- /* And a maximizer */
- if (mode & MAXIMIZER) {
- mvwaddch(_wintree->win, 0, _wintree->win->_maxx - (1 + i), ']');
- mvwaddch(_wintree->win, 0, _wintree->win->_maxx - (2 + i), ACS_UARROW);
- mvwaddch(_wintree->win, 0, _wintree->win->_maxx - (3 + i), '[');
- }
-
- /* And the sizer stuff */
- if (mode & SIZER) {
- mvwaddch(_wintree->win, 0, 0, ACS_ULCORNER);
- mvwaddch(_wintree->win, 0, _wintree->win->_maxx, ACS_URCORNER);
- mvwaddch(_wintree->win, _wintree->win->_maxy, 0, ACS_LLCORNER);
- mvwaddch(_wintree->win, _wintree->win->_maxy, _wintree->win->_maxx, ACS_LRCORNER);
- }
-
- if (_wintree->callback)
- (_wintree->callback)(_wintree->workwin, WM_CREATED);
-
- Win_PlaySound(SOUND_OPEN);
- }
-
- void _add_window_link(void)
- {
- /* Allocate a new window structure for the next window */
- _wintree->next = (WIN *) malloc(_winstruct_length());
-
- /* Point the previous window pointer of the next window here, so we
- have a place to backtrack to. */
- _wintree->next->prev = _wintree;
-
- /* Increase our global pointer to point to the new window */
- _wintree = _wintree->next;
-
- /* And make sure this window can't go off into nowheresville */
- _wintree->next = NULL;
- }
-
- void _delete_window_link(void)
- {
- if (_wintree->prev)
- _wintree->prev->next = _wintree->next;
-
- if (_wintree->next)
- _wintree->next->prev = _wintree->prev;
-
- free(_wintree);
-
- if (_wintree->prev)
- _wintree = _wintree->prev;
- else if (_wintree->next)
- _wintree = _wintree->next;
- else {
- _wintree = (WIN *) malloc(sizeof(_winstruct_length()));
- _wintree->prev = NULL;
- _wintree->next = NULL;
- }
- }
-
- int _get_window_index(Gpm_Event *event)
- {
- int idx = -1;
-
- if (_moving_idx == -1) {
- _top_window_link();
-
- while(_wintree->next) {
- if ((event->y >= _wintree->win->_begy) &&
- (event->y <= (_wintree->win->_begy + _wintree->win->_maxy)) &&
- (event->x >= _wintree->win->_begx) &&
- (event->x <= (_wintree->win->_begx + _wintree->win->_maxx)))
- idx = _wintree->index;
-
- _wintree = _wintree->next;
- }
- } else
- idx = _moving_idx;
-
- return(idx);
- }
-
- void _minimize_window(void)
- {
- Win_PlaySound(SOUND_MINIMIZE);
- if (_wintree->callback)
- (_wintree->callback)(_wintree->workwin, WM_MINIMIZED);
- }
-
- void _maximize_window(void)
- {
- Win_PlaySound(SOUND_MAXIMIZE);
- if (_wintree->callback)
- (_wintree->callback)(_wintree->workwin, WM_MAXIMIZED);
- }
-
- void _move_window(Gpm_Event *event)
- {
- int x = event->x, y = event->y;
-
- x -= _xoffset;
-
- if (y > (_main_win->_maxy - _wintree->win->_maxy + 1))
- y = (_main_win->_maxy - _wintree->win->_maxy + 1);
- if (x > (_main_win->_maxx - _wintree->win->_maxx))
- x = (_main_win->_maxx - _wintree->win->_maxx);
-
- if (x < 0)
- x = 0;
-
- if (y < 1)
- y = 1;
-
- _wintree->cur.x = x;
- _wintree->cur.y = y;
-
- move_panel(_wintree->pan, y, x);
- move_panel(_wintree->workpan, y + 1, x + 1);
-
- if (_wintree->callback)
- (_wintree->callback)(_wintree->workwin, WM_MOVED);
- }
-
- /* Ugh! This is sloppy code, but it works quite well. I need to optimize
- this a bit and make it more readable. :) */
- void _handle_window_coords(Gpm_Event *event)
- {
- int i = 1, x = 1;
-
- if (_wintree->mode & CLOSER) {
- if ((event->x == _wintree->win->_begx + 2) &&
- (event->y == _wintree->win->_begy) &&
- (_moving_win == FALSE) &&
- (event->buttons & GPM_B_LEFT)) {
- if (_wintree->callback)
- (_wintree->callback)(WM_DELETED);
- Win_PlaySound(SOUND_CLOSE);
- del_panel(_wintree->pan);
- del_panel(_wintree->workpan);
- delwin(_wintree->win);
- delwin(_wintree->workwin);
- _delete_window_link();
- }
-
- x = 4;
- }
-
- if (_wintree->mode & MINIMIZER) {
- if ((event->x == (_wintree->win->_begx + _wintree->win->_maxx) - 2) &&
- (event->y == _wintree->win->_begy) &&
- (_moving_win == FALSE) &&
- (event->buttons & GPM_B_LEFT) &&
- (!(event->type & (GPM_DRAG | GPM_UP))))
- _minimize_window();
-
- i = 4;
- }
-
- if (_wintree->mode & MAXIMIZER) {
- if ((event->x == (_wintree->win->_begx + _wintree->win->_maxx) - (1 + i)) &&
- (event->y == _wintree->win->_begy) &&
- (_moving_win == FALSE) &&
- (event->buttons & GPM_B_LEFT) &&
- (!(event->type & (GPM_DRAG | GPM_UP))))
- _maximize_window();
- }
-
- if ((_wintree->mode & MOVER) || (_moving_win)) {
- if ((event->x >= (_wintree->win->_begx + x)) &&
- (event->x <= (_wintree->win->_begx + _wintree->win->_maxx - i)) &&
- (event->y == _wintree->win->_begy) &&
- (_moving_win == FALSE) &&
- (event->buttons & GPM_B_LEFT) &&
- (event->type & GPM_DOWN)) {
- _xoffset = event->x - _wintree->win->_begx;
- _moving_win = TRUE;
- _moving_idx = _wintree->index;
- }
-
- if ((_moving_win) && (event->buttons & GPM_B_LEFT) &&
- (event->type & GPM_DRAG))
- _move_window(event);
- }
-
- if ((event->buttons & GPM_B_LEFT) && (event->type & GPM_UP)) {
- _xoffset = 0;
- _moving_win = FALSE;
- _moving_idx = -1;
- }
- }
-
- void _handle_window(Gpm_Event *event)
- {
- int findidx = _get_window_index(event);
-
- _top_window_link();
- _cur_window = findidx;
-
- while(_wintree->next) {
- if ((_wintree->index == _cur_window) &&
- (_cur_window != -1)) {
- _handle_window_coords(event);
- return;
- }
-
- _wintree = _wintree->next;
- }
- }
-
- WINDOW *Win_CreateWindow(int x, int y, int w, int h, char *title, int mode,
- void *callback)
- {
- WINDOW *ourwin;
- int idx;
-
- _bottom_window_link();
-
- if (_wintree->prev)
- idx = _wintree->prev->index + 1;
- else
- idx = 1;
-
- _has_win = TRUE;
-
- _wintree->title = (char *) malloc(strlen(title));
- _wintree->mode = mode;
- _wintree->index = idx;
- _wintree->callback = callback;
- strcpy(_wintree->title, title);
-
- _create_window(x, y, w, h, title, mode);
- ourwin = _wintree->workwin;
-
- _add_window_link();
-
- return(ourwin);
- }
-